<template lang="html">
  <div class="yo-scroll"
       :class="{touch:touching}"
       @touchstart="touchStart($event)"
       @touchmove="touchMove($event)"
       @touchend="touchEnd($event)"
       @scroll="(onInfinite || infiniteLoading) ? onScroll($event) : undefined">
    <section class="inner" :style="{ transform: 'translate3d(0, ' + top + 'px, 0)' }">
      <header class="pull-refresh">
        <slot name="pull-refresh">
            <div id="loading">
              <div id="loading-center">
                <div class="object" id="object_one"></div>
                <div class="object" id="object_two"></div>
                <div class="object" id="object_three"></div>
              </div>
            </div>
        </slot>
      </header>
      <slot></slot>
      <footer v-if="enableInfinite" class="load-more">
        <slot name="load-more">
          <span>加载中……</span>
        </slot>
      </footer>
    </section>
  </div>
</template>

<script>
  export default {
    props: {
      offset: {
        type: Number,
        default: 180
      },
      enableInfinite: {
        type: Boolean,
        default: true
      },
      enableRefresh: {
        type: Boolean,
        default: true
      },
      onRefresh: {
        type: Function,
        default: undefined,
        required: false
      },
      onInfinite: {
        type: Function,
        default: undefined,
        require: false
      },
    },
    data() {
      return {
        top: 0,
        state: 0,
        startY: 0,
        touching: false,
        infiniteLoading: false
      }
    },
    methods: {
      touchStart(e) {
        this.startY = e.targetTouches[0].pageY
        this.startScroll = this.$el.scrollTop || 0
        this.touching = true
      },
      touchMove(e) {
        if (!this.enableRefresh || this.$el.scrollTop > 0 || !this.touching) {
          return
        }
        let diff = e.targetTouches[0].pageY - this.startY - this.startScroll
        if (diff > 0) e.preventDefault()
        this.top = Math.pow(diff, 0.8) + (this.state === 2 ? this.offset : 0)

        if (this.state === 2) { // in refreshing
          return
        }
        if (this.top >= this.offset) {
          this.state = 1
        } else {
          this.state = 0
        }
      },
      touchEnd(e) {
        if (!this.enableRefresh) return
        this.touching = false
        if (this.state === 2) { // in refreshing
          this.state = 2
          this.top = this.offset
          return
        }
        if (this.top >= this.offset) { // do refresh
          this.refresh()
        } else { // cancel refresh
          this.state = 0
          this.top = 0
        }
      },
      refresh() {
        this.state = 2
        this.top = this.offset
        setTimeout(() => { // 在次做延迟  模拟请求
          this.onRefresh(this.refreshDone)
        }, 1500)

      },
      refreshDone() {
        this.state = 0
        this.top = 0
      },

      infinite() {
        this.infiniteLoading = true
        this.onInfinite(this.infiniteDone)
      },

      infiniteDone() {
        this.infiniteLoading = false
      },

      onScroll(e) {
        if (!this.enableInfinite || this.infiniteLoading) {
          return
        }
        let outerHeight = this.$el.clientHeight;
        let innerHeight = this.$el.querySelector('.inner').clientHeight;
        let scrollTop = this.$el.scrollTop;
        let ptrHeight = this.onRefresh ? this.$el.querySelector('.pull-refresh').clientHeight : 0;
        let infiniteHeight = this.$el.querySelector('.load-more').clientHeight;
        let bottom = innerHeight - outerHeight - scrollTop - ptrHeight;
        if (bottom < infiniteHeight) this.infinite();
      }
    }
  }
</script>
<style >
  .yo-scroll {
    position: absolute;
    top: 0px;
    right: 0;
    bottom: 94px;
    left: 0;
    overflow: auto;
    -webkit-overflow-scrolling: touch;
    background-color: rgb(255,255,255);
  }

  .yo-scroll .inner {
    position: absolute;
    top: -2rem;
    width: 100%;
    transition-duration: 300ms;
  }

  .yo-scroll .pull-refresh {
    position: relative;
    left: 0;
    top: 100px;
    width: 100%;
    height: 2rem;
    display: flex;
    align-items: center;
    justify-content: center;
  }

  .yo-scroll.touch .inner {
    transition-duration: 0ms;
  }


  .yo-scroll .load-more {
    height: 3rem;
    display: flex;
    align-items: center;
    justify-content: center;
  }
/* 加载动画 */

  #loading-center{
    width: 100%;
    height: 100%;
    position: relative;
  }

  .object{
    width: 20px;
    height: 20px;
    background-color: rgb(190, 66, 64);
    float: left;
    margin-right: 20px;
    margin-top: 65px;
    -moz-border-radius: 50% 50% 50% 50%;
    -webkit-border-radius: 50% 50% 50% 50%;
    border-radius: 50% 50% 50% 50%;
  }

  #object_one {
    -webkit-animation: object_one 1.1s infinite;
    animation: object_one 1.1s infinite;
  }
  #object_two {
    -webkit-animation: object_two 1.1s infinite;
    animation: object_two 1.1s infinite;
    -webkit-animation-delay: 0.25s;
    animation-delay: 0.25s;
  }
  #object_three {
    -webkit-animation: object_three 1.1s infinite;
    animation: object_three 1.1s infinite;
    -webkit-animation-delay: 0.5s;
    animation-delay: 0.5s;
  }
  @-webkit-keyframes object_one {  70% { -webkit-transform: scale(0); }  }
  @keyframes object_one {  70% { transform: scale(0);  -webkit-transform: scale(0); }  }
  @-webkit-keyframes object_two { 70% { -webkit-transform: scale(0); }}
  @keyframes object_two {70% {  transform: scale(0); -webkit-transform:  scale(0);} }
  @-webkit-keyframes object_three { 70% { -webkit-transform: scale(0); } }
  @keyframes object_three { 70% { transform: scale(0);  -webkit-transform: scale(0);} }


</style>
